package com.kingyea.mobilepolice.security;

import com.kingyea.mobilepolice.permission.service.PermissionService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.ConfigAttribute;
import org.springframework.security.web.FilterInvocation;
import org.springframework.security.web.access.intercept.FilterInvocationSecurityMetadataSource;
import org.springframework.security.web.util.matcher.AntPathRequestMatcher;
import org.springframework.security.web.util.matcher.RequestMatcher;

import javax.servlet.http.HttpServletRequest;
import java.util.*;
import java.util.concurrent.ConcurrentLinkedQueue;

/**
 * @author cxc
 * @version v1.0.0
 * @description
 * @date Created in 2018.04.01 17:29
 */

public class MyFilterInvocationSecurityMetadataSource implements FilterInvocationSecurityMetadataSource {

    private static Map<String, Collection<ConfigAttribute>> roleResourceMap = new HashMap<>();
    private static Collection<ConfigAttribute> configAttributeList = new ConcurrentLinkedQueue<>();
    //private RoleResourcesService roleResourcesService;

    /**
     * 构造方法
     */
    @Autowired
    public MyFilterInvocationSecurityMetadataSource(PermissionService permissionService) {//RoleResourcesService roleResourcesService){
        //this.roleResourcesBeans = roleResourcesBeans;
        //this.roleResourcesService = roleResourcesService;
//        loadResourceDefine();
        roleResourceMap = permissionService.allPermissionRolesMap();
    }

    /**
     * -------------【全大写】
     * 因为只有权限控制的资源才需要被拦截验证,所以只加载有权限控制的资源
     * (也可以把所有不需要控制的资源给予游客角色)
     * <p>
     * RoleResourcesBean
     */
    /*private void loadResourceDefine(){
        roleResourcesBeans.stream().forEach(bean -> {
            ConfigAttribute roleStr = new SecurityConfig(bean.getRole().toUpperCase());
            if(!configAttributeList.contains(roleStr))//去重复
                configAttributeList.add(roleStr);
            String url = bean.getUrl();
            if(roleResourceMap.containsKey(url)){
                Collection<ConfigAttribute> value = roleResourceMap.get(url);
                value.add(roleStr);
                roleResourceMap.put(url,value);

            }else {
                roleResourceMap.put(url, Lists.newArrayList(roleStr));
            }
        });
    }*/
    public static void main(String[] args) {
//        roleResourceMap.containsKey(1);
//        String url = "/a/123/b";
//        String urlM = "/a/\\w*/b";
//        System.out.println(url.matches(urlM));
        Map<String, String> map = new HashMap<>();
        map.put("/a/\\w*", "ROLE_ADMIN");

        String url = "/a/123.j";
        Optional<String> opKey = map.keySet().stream().filter(key -> url.matches(key)).findFirst();
        if (opKey.isPresent()) {
            String anyKey = opKey.get();
            System.out.println(map.get(anyKey));
            System.out.println(map.containsKey(anyKey));
        }
        System.out.println(opKey);
    }

    /**
     * 根据url获取需要的角色集合
     */
    @Override
    public Collection<ConfigAttribute> getAttributes(Object urlObject) throws IllegalArgumentException {
        HttpServletRequest request = ((FilterInvocation) urlObject).getRequest();
        Iterator<String> ite = roleResourceMap.keySet().iterator();
        while (ite.hasNext()) {
            String resURL = ite.next();
            RequestMatcher requestMatcher = new AntPathRequestMatcher(resURL);
            if (requestMatcher.matches(request)) {
                return roleResourceMap.get(resURL);//对应url拿到需要的访问权限角色
            }
        }
        return null;
    }

    @Override
    public Collection<ConfigAttribute> getAllConfigAttributes() {
        return configAttributeList;
    }

    @Override
    public boolean supports(Class<?> clazz) {
        return clazz.equals(ConfigAttribute.class);
    }

}
